package com.sky.service.impl;

import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.sky.constant.MessageConstant;
import com.sky.context.BaseContext;
import com.sky.dto.*;
import com.sky.entity.*;
import com.sky.exception.AddressBookBusinessException;
import com.sky.exception.OrderBusinessException;
import com.sky.exception.ShoppingCartBusinessException;
import com.sky.mapper.AddressBookMapper;
import com.sky.mapper.OrderDetailMapper;
import com.sky.mapper.OrderMapper;
import com.sky.mapper.ShoppingCartMapper;
import com.sky.result.PageResult;
import com.sky.result.Result;
import com.sky.service.BaiduMapService;
import com.sky.service.OrderService;
import com.sky.utils.JwtUtil;
import com.sky.vo.OrderDetailVO;
import com.sky.vo.OrderPaymentVO;
import com.sky.vo.OrderStatisticsVO;
import com.sky.vo.OrderSubmitVO;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.RandomStringUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PutMapping;

import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
@Slf4j
public class OrderServiceImpl implements OrderService {
    @Autowired
    private OrderMapper orderMapper;
    @Autowired
    private OrderDetailMapper orderDetailMapper;
    @Autowired
    private AddressBookMapper addressBookMapper;
    @Autowired
    private ShoppingCartMapper shoppingCartMapper;
    @Autowired
    private BaiduMapService baiduMapService;


    //用户下单
    @Transactional
    @Override
    public OrderSubmitVO submitOrder(OrdersSubmitDTO orderSubmitDTO) {
        //处理业务异常(地址簿为空,购物车为空)
        //判断地址簿是否存在
        AddressBook addressBook = addressBookMapper.getById(orderSubmitDTO.getAddressBookId());
        if (addressBook == null) {
            throw new AddressBookBusinessException(MessageConstant.ADDRESS_BOOK_IS_NULL);
        }
        //判断地址是否在配送范围内
        boolean withinRange = baiduMapService.checkDeliveryRange(addressBook);
        if (!withinRange) {
            throw new OrderBusinessException(MessageConstant.OUT_OF_DELIVERY_RANGE);
        }


        //判断购物车是否存在
        Long userId = BaseContext.getCurrentId();
        ShoppingCart shoppingCart = new ShoppingCart();
        shoppingCart.setUserId(userId);
        List<ShoppingCart> shoppingCartList = shoppingCartMapper.list(shoppingCart);
        if (shoppingCartList == null || shoppingCartList.size() == 0) {
            throw new ShoppingCartBusinessException(MessageConstant.SHOPPING_CART_IS_NULL);
        }
        //向订单表插入一条数据
        Orders orders = new Orders();
        BeanUtils.copyProperties(orderSubmitDTO, orders);
        orders.setUserId(userId);
        orders.setOrderTime(LocalDateTime.now());
        orders.setPayStatus(Orders.UN_PAID);
        orders.setStatus(Orders.PENDING_PAYMENT);
        orders.setPhone(addressBook.getPhone());
        orders.setConsignee(addressBook.getConsignee());
        orders.setAddress(addressBook.getDetail()); // 添加这一行，设置地址信息
        orders.setNumber(String.valueOf(System.currentTimeMillis()));
        orderMapper.insert(orders);


        List<OrderDetail> orderDetailList = new ArrayList<>();
        //向订单明细表插入n条数据
        for (ShoppingCart cart : shoppingCartList) {
            OrderDetail orderDetail = new OrderDetail();
            BeanUtils.copyProperties(cart, orderDetail);
            orderDetail.setOrderId(orders.getId());
            orderDetailList.add(orderDetail);
        }
        orderDetailMapper.insertBatch(orderDetailList);

        //清空当前用户的购物车
        shoppingCartMapper.clean(userId);

        //封装VO返回结果
        OrderSubmitVO orderSubmitVO = OrderSubmitVO.builder()
                .id(orders.getId())
                .orderNumber(orders.getNumber())
                .orderAmount(orders.getAmount())
                .orderTime(orders.getOrderTime())
                .build();

        return orderSubmitVO;
    }

    /**
     * 订单支付成功
     * @param ordersPaymentDTO
     */
    @Override
    @Transactional
    public OrderPaymentVO paySuccess(OrdersPaymentDTO ordersPaymentDTO) {
        // 1.记录完整的支付请求信息
        log.info("收到支付成功请求: {}", ordersPaymentDTO);
        
        // 1.查询订单，结合用户ID和订单号进行查询
        String orderNumber = ordersPaymentDTO.getOrderNumber();
        Integer payMethod = ordersPaymentDTO.getPayMethod();
        log.info("支付成功，查询订单：订单号={}, 支付方式={}", orderNumber, payMethod);
        
        // 获取当前登录用户ID
        Long userId = BaseContext.getCurrentId();
        log.info("当前登录用户ID: {}", userId);
        
        // 验证订单号格式是否正确
        if (orderNumber == null || orderNumber.trim().isEmpty()) {
            log.error("订单号为空: {}", ordersPaymentDTO);
            throw new OrderBusinessException("订单号无效");
        }
        
        // 增强查询逻辑，同时使用订单号和用户ID进行查询
        Map<String, Object> params = new HashMap<>();
        params.put("orderNumber", orderNumber);
        params.put("userId", userId); // 增加用户ID作为查询条件
        
        // 查询订单并记录详细信息
        Orders orders = orderMapper.getByNumberAndUserId(params);
        
        // 如果根据用户ID和订单号未查询到订单，尝试只根据订单号查询（兼容旧逻辑）
        if (orders == null) {
            log.warn("未找到用户 {} 的订单: {}, 尝试只根据订单号查询", userId, orderNumber);
            params.clear();
            params.put("orderNumber", orderNumber);
            orders = orderMapper.getByNumber(params);
        }
        
        if (orders == null) {
            log.error("未找到订单：订单号={}", orderNumber);
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        
        // 记录订单当前状态
        log.info("查询到订单，ID={}, 当前状态：status={}, payStatus={}", 
                orders.getId(), orders.getStatus(), orders.getPayStatus());
        
        // 2.创建更新对象
        Orders updateOrder = new Orders();
        updateOrder.setId(orders.getId()); // 确保使用正确的id
        updateOrder.setStatus(Orders.TO_BE_CONFIRMED); // 待接单状态
        updateOrder.setPayStatus(Orders.PAID);         // 已支付状态
        updateOrder.setCheckoutTime(LocalDateTime.now());
        updateOrder.setPayMethod(payMethod);
        
        // 确保状态字段不为null
        if (updateOrder.getStatus() == null) {
            log.error("订单状态为null，设置默认值");
            updateOrder.setStatus(Orders.TO_BE_CONFIRMED);
        }
        if (updateOrder.getPayStatus() == null) {
            log.error("支付状态为null，设置默认值");
            updateOrder.setPayStatus(Orders.PAID);
        }
        
        // 记录要更新的订单信息
        log.info("准备更新订单状态：订单ID={}, 目标状态：status={}, payStatus={}", 
                updateOrder.getId(), updateOrder.getStatus(), updateOrder.getPayStatus());
        
        // 执行更新
        int updateCount = orderMapper.update(updateOrder);
        log.info("标准更新执行结果：更新行数={}", updateCount);
        
        if (updateCount > 0) {
            log.info("订单状态更新成功，新状态：status={}, payStatus={}, 更新行数：{}", 
                    updateOrder.getStatus(), updateOrder.getPayStatus(), updateCount);
        } else {
            log.error("订单状态更新失败，未找到匹配的订单或状态未变化：status={}, payStatus={}, 订单ID={}", 
                     updateOrder.getStatus(), updateOrder.getPayStatus(), updateOrder.getId());
            
            // 手动强制更新，避免因为MyBatis动态SQL问题导致更新失败
            Map<String, Object> forceUpdateParams = new HashMap<>();
            forceUpdateParams.put("id", updateOrder.getId());
            forceUpdateParams.put("status", updateOrder.getStatus());
            forceUpdateParams.put("payStatus", updateOrder.getPayStatus());
            forceUpdateParams.put("checkoutTime", updateOrder.getCheckoutTime());
            forceUpdateParams.put("payMethod", updateOrder.getPayMethod());
            
            log.info("执行强制更新：{}", forceUpdateParams);
            orderMapper.forceUpdateOrder(forceUpdateParams);
            log.info("已尝试强制更新订单状态");
            
            // 验证强制更新是否成功
            Orders updatedOrder = orderMapper.getById(updateOrder.getId());
            if (updatedOrder != null) {
                log.info("强制更新后订单状态：status={}, payStatus={}", 
                        updatedOrder.getStatus(), updatedOrder.getPayStatus());
            } else {
                log.error("强制更新后无法查询到订单，订单ID={}", updateOrder.getId());
            }
        }
        
        // 3.返回模拟支付数据
        return OrderPaymentVO.builder()
                .nonceStr(RandomStringUtils.randomAlphanumeric(32))
                .timeStamp(String.valueOf(System.currentTimeMillis()/1000))
                .packageStr("prepay_id=SIMULATED_"+orderNumber)
                .signType("RSA")
                .estimatedDeliveryTime(String.valueOf(orders.getEstimatedDeliveryTime()))
                .paySign("SIMULATED_SIGN_"+
                    RandomStringUtils.randomAlphanumeric(32).toUpperCase())
                .build();
    }

    //查询订单详情
    @Override
    @Transactional
    public OrderDetailVO orderDetail(Long id) {
        // 1.查询订单
        Orders orders = orderMapper.getById(id);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        
        // 2.如果地址为空，则从地址簿获取
        if (orders.getAddress() == null || orders.getAddress().isEmpty()) {
            // 获取用户的地址簿
            AddressBook addressBook = new AddressBook();
            addressBook.setUserId(orders.getUserId());
            addressBook.setIsDefault(1); // 获取默认地址
            List<AddressBook> addressBooks = addressBookMapper.list(addressBook);
            
            // 如果没有默认地址，获取第一个地址
            if (addressBooks != null && !addressBooks.isEmpty()) {
                AddressBook defaultAddress = addressBooks.get(0);
                orders.setAddress(defaultAddress.getDetail());
                orders.setPhone(defaultAddress.getPhone());
                orders.setConsignee(defaultAddress.getConsignee());
            }
        }
        
        //3.查询订单详情
        List<OrderDetail> orderDetailList = orderDetailMapper.getByOrderId(id);
        if (orderDetailList == null || orderDetailList.size() == 0) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //4.封装VO返回结果
        OrderDetailVO orderDetailVO = new OrderDetailVO();
        BeanUtils.copyProperties(orders, orderDetailVO);
        orderDetailVO.setOrderDetailList(orderDetailList);
    
        return orderDetailVO;
    }

    //分页查询历史订单
    @Override
    public PageResult pageQuery(OrdersPageQueryDTO ordersPageQueryDTO) {
        log.info("分页查询历史订单，参数：{}", ordersPageQueryDTO);
        // 启动分页
        PageHelper.startPage(ordersPageQueryDTO.getPage(), ordersPageQueryDTO.getPageSize());
        
        // 查询订单列表
        Page<OrdersAndDetail> page = orderMapper.pageQuery(ordersPageQueryDTO);
        log.info("查询到的订单数量：{}", page.getTotal());

        
        // 获取订单列表数据
        List<OrdersAndDetail> ordersList = page.getResult();
        log.info("当前页订单数量：{}", ordersList.size());

        // 为每个订单查询并设置地址信息
        for (OrdersAndDetail orders : ordersList) {
            Long userId = orders.getUserId();
            AddressBook addressBook = new AddressBook();
            addressBook.setUserId(userId);
            List<AddressBook> list = addressBookMapper.list(addressBook);
            for (AddressBook book : list) {
                String detail = book.getDetail();
                orders.setAddress(detail);
            }




        
//        // 为每个订单查询并设置订单明细
//        for (OrdersAndDetail orders : ordersList) {
            // 获取订单id
            Long orderId = orders.getId();
            log.info("为订单id: {} 查询订单明细", orderId);

            
            // 根据订单id查询订单明细
            List<OrderDetail> orderDetailList = orderDetailMapper.getByOrderId(orderId);
            
            // 确保即使没有订单明细也返回空列表而不是null
            if (orderDetailList == null) {
                orderDetailList = new ArrayList<>();
                log.info("订单id: {} 没有找到订单明细", orderId);
            } else {
                log.info("订单id: {} 查询到 {} 条订单明细", orderId, orderDetailList.size());
            }
            
            // 修改：使用单数形式的字段名，与前端保持一致
            orders.setOrderDetailList(orderDetailList);  // 修改为 setOrderDetailList
        }
        
        // 直接使用构造函数创建PageResult对象
        return new PageResult(page.getTotal(), ordersList);
    }

    /**
     * 取消订单
     * @param id
     */
    @Override
    public void cancel(Long id) {
        // 1.查询订单
        Orders orders = orderMapper.getById(id);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        // 2.取消订单(修改订单状态)
        // 2.1 取消订单
        orders.setCancelTime(LocalDateTime.now());
        orders.setStatus(Orders.CANCELLED);
        orderMapper.update(orders);
        // 2.2 退款 更新订单支付状态
        orders.setPayStatus(Orders.REFUND);
        orderMapper.update(orders);
    }

    /**
     * 再来一单
     * @param id
     */
    @Override
    public void repetition(Long id) {
        //1.根据订单id查询历史订单
        Orders orders = orderMapper.getById(id);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //2.根据历史订单查询订单明细
        List<OrderDetail> orderDetailList = orderDetailMapper.getByOrderId(id);
        if (orderDetailList == null || orderDetailList.size() == 0) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        
        //3.获取当前用户id
        Long userId = BaseContext.getCurrentId();
        
        //4.清空当前用户的购物车
        shoppingCartMapper.clean(userId);
        
        //5.将历史订单明细转换为购物车项
        List<ShoppingCart> shoppingCartList = new ArrayList<>();
        for (OrderDetail orderDetail : orderDetailList) {
            ShoppingCart shoppingCart = new ShoppingCart();
            BeanUtils.copyProperties(orderDetail, shoppingCart);
            shoppingCart.setUserId(userId);
            shoppingCart.setCreateTime(LocalDateTime.now());
            shoppingCartList.add(shoppingCart);
        }
        
        //6.批量添加到购物车
        shoppingCartMapper.insertBatch(shoppingCartList);


    }


    /**
     * 各个状态的订单数量统计
     * @return
     */
    @Override
    public OrderStatisticsVO getstatistics() {
        Long userId = BaseContext.getCurrentId();
        OrdersPageQueryDTO ordersPageQueryDTO = new OrdersPageQueryDTO();
        ordersPageQueryDTO.setUserId(userId);
        PageResult pageResult = pageQuery(ordersPageQueryDTO);
        List<OrdersAndDetail> ordersList = (List<OrdersAndDetail>) pageResult.getRecords();
        OrderStatisticsVO orderStatisticsVO = new OrderStatisticsVO();
    
        for (OrdersAndDetail order : ordersList) {
            Integer status = order.getStatus();
            if (status == Orders.CONFIRMED) {
                orderStatisticsVO.setConfirmed(orderStatisticsVO.getConfirmed() + 1);
            } else if (status == Orders.DELIVERY_IN_PROGRESS) {
                orderStatisticsVO.setDeliveryInProgress(orderStatisticsVO.getDeliveryInProgress() + 1);
            } else if (status == Orders.TO_BE_CONFIRMED) { // 修改此处，将TO_BE_CONFIRMED计入待接单
                orderStatisticsVO.setToBeConfirmed(orderStatisticsVO.getToBeConfirmed() + 1);
            }
            // 可以添加对PAID状态的处理
        }
        return orderStatisticsVO;
    }


    /**
     * 接单
     * @param id1
     */
    @Override
    public void confirm(Long id1) {
        //1.根据订单id查询订单
        Orders orders;
        orders = orderMapper.getById(id1);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //2.修改订单状态
        orders.setStatus(Orders.CONFIRMED);
        orderMapper.update(orders);
    }


    /**
     * 拒单
     * @param ordersRejectionDTO
     */
    @Override
    public void reject(OrdersRejectionDTO ordersRejectionDTO) {
        //1.根据订单id查询订单
        Orders orders;
        orders = orderMapper.getById(ordersRejectionDTO.getId());
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //2.根据拒绝原因修改订单状态
        orders.setStatus(Orders.CANCELLED);
        orders.setRejectionReason(ordersRejectionDTO.getRejectionReason());
        orderMapper.update(orders);
    }
    
    /**
     * 确认支付成功
     * @param ordersPaymentDTO
     * @return
     */
    @Override
    @Transactional
    public Orders confirmPaySuccess(OrdersPaymentDTO ordersPaymentDTO) {
        // 1.记录完整的支付确认请求信息
        log.info("收到支付确认请求: {}", ordersPaymentDTO);
        
        // 2.查询订单，结合用户ID和订单号进行查询
        String orderNumber = ordersPaymentDTO.getOrderNumber();
        Integer payMethod = ordersPaymentDTO.getPayMethod();
        log.info("支付确认，查询订单：订单号={}, 支付方式={}", orderNumber, payMethod);
        
        // 获取当前登录用户ID
        Long userId = BaseContext.getCurrentId();
        log.info("当前登录用户ID: {}", userId);
        
        // 验证订单号格式是否正确
        if (orderNumber == null || orderNumber.trim().isEmpty()) {
            log.error("订单号为空: {}", ordersPaymentDTO);
            throw new OrderBusinessException("订单号无效");
        }
        
        // 增强查询逻辑，同时使用订单号和用户ID进行查询
        Map<String, Object> params = new HashMap<>();
        params.put("orderNumber", orderNumber);
        params.put("userId", userId); // 增加用户ID作为查询条件
        
        // 查询订单并记录详细信息
        Orders orders = orderMapper.getByNumberAndUserId(params);
        
        // 如果根据用户ID和订单号未查询到订单，尝试只根据订单号查询（兼容旧逻辑）
        if (orders == null) {
            log.warn("未找到用户 {} 的订单: {}, 尝试只根据订单号查询", userId, orderNumber);
            params.clear();
            params.put("orderNumber", orderNumber);
            orders = orderMapper.getByNumber(params);
        }
        
        if (orders == null) {
            log.error("未找到订单：订单号={}", orderNumber);
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        
        // 记录订单当前状态
        log.info("查询到订单，ID={}, 当前状态：status={}, payStatus={}", 
                orders.getId(), orders.getStatus(), orders.getPayStatus());
        
        // 3.创建更新对象，强制更新订单状态
        Orders updateOrder = new Orders();
        updateOrder.setId(orders.getId()); // 确保使用正确的id
        updateOrder.setStatus(Orders.TO_BE_CONFIRMED); // 待接单状态
        updateOrder.setPayStatus(Orders.PAID);         // 已支付状态
        updateOrder.setCheckoutTime(LocalDateTime.now());
        updateOrder.setPayMethod(payMethod);
        
        // 确保状态字段不为null
        if (updateOrder.getStatus() == null) {
            log.error("订单状态为null，设置默认值");
            updateOrder.setStatus(Orders.TO_BE_CONFIRMED);
        }
        
        log.info("准备更新订单状态，ID={}，更新前状态：status={}, payStatus={}", 
                orders.getId(), orders.getStatus(), orders.getPayStatus());
        log.info("更新后状态：status={}, payStatus={}", 
                updateOrder.getStatus(), updateOrder.getPayStatus());
        
        // 4.执行更新操作，使用forceUpdateOrder确保所有字段都被更新
        Map<String, Object> updateParams = new HashMap<>();
        updateParams.put("id", orders.getId());
        updateParams.put("status", updateOrder.getStatus());
        updateParams.put("payStatus", updateOrder.getPayStatus());
        updateParams.put("checkoutTime", updateOrder.getCheckoutTime());
        updateParams.put("payMethod", updateOrder.getPayMethod());
        
        log.info("执行强制更新订单状态，参数：{}", updateParams);
        orderMapper.forceUpdateOrder(updateParams);
        log.info("订单状态强制更新完成，ID={}", orders.getId());
        
        // 5.重新查询订单，获取最新状态
        Orders updatedOrder = orderMapper.getById(orders.getId());
        log.info("订单最新状态：status={}, payStatus={}", updatedOrder.getStatus(), updatedOrder.getPayStatus());
        
        // 6.返回更新后的订单信息
        return updatedOrder;
    }

    /**
     * 派送订单
     * @param id
     */
    @Override
    public void delivery(Long id) {
        //1.根据订单id查询订单
        Orders orders;
        orders = orderMapper.getById(id);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //2.修改订单状态
        orders.setStatus(Orders.DELIVERY_IN_PROGRESS);
        orderMapper.update(orders);
    }

    /**
     * 完成订单
     * @param id
     */
    @Override
    public void complete(Long id) {
        //1.根据订单id查询订单
        Orders orders;
        orders = orderMapper.getById(id);
        if (orders == null) {
            throw new OrderBusinessException(MessageConstant.ORDER_NOT_FOUND);
        }
        //2.修改订单状态
        orders.setStatus(Orders.COMPLETED);
        orderMapper.update(orders);
    }


}
